#!/usr/bin/env python2
# -*- coding: utf-8 -*-
"""
@author: Felipe Espic

DESCRIPTION:
This script extracts low-dimensional acoustic features from a batch of wav files intended for using with the Merlin toolkit.
It runs the extraction in parallel mode, using all the cores available in the system.

The acoustic features extracted and used by Merlin are:
- '<file>.mag'  : Mel-scaled Log-Mag (dim=nbins_mel,   usually 60).
- '<file>.real' : Mel-scaled real    (dim=nbins_phase, usually 45).
- '<file>.imag' : Mel-scaled imag    (dim=nbins_phase, usually 45).
- '<file>.lf0'  : Log-F0 (dim=1).

Also, this script extracts the additional files:
- '<file>.est'  : File generated by REAPER containing epoch locations and voi/unvoi decisions (remove them if wanted).
- '<file>.shift': File that contains the shifts (hop-sizes) for each extracted frame (variable frame rate).
                  It is used to modify the label files in Merlin. Se .... for more information.

INSTRUCTIONS:
This demo should work out of the box. Just run it by typing: python <script name>
If wanted, you can modify the input options (directories, input files, etc.) See the main function below for details.
"""

import sys, os

if len(sys.argv)!=5:
    print("Usage: ")
    print("python extract_features_for_merlin.py <path_to_merlin_dir> <path_to_wav_dir> <path_to_feat_dir> <sampling rate>")
    sys.exit(1)

# top merlin directory
merlin_dir = sys.argv[1]

# input audio directory
wav_dir = sys.argv[2]

# Output features directory
out_dir = sys.argv[3]

# Expected sample rate
fs_expected = int(sys.argv[4])

# Magphase directory
magphase = os.path.join(merlin_dir, 'tools', 'magphase', 'src')
sys.path.append(os.path.realpath(magphase))
import libutils as lu
import magphase as mp


def feat_extraction(wav_file, out_feats_dir):

    # Parsing path:
    file_name_token = os.path.basename(os.path.splitext(wav_file)[0])

    # Display:
    print("\nAnalysing file: " + file_name_token + '.wav' + '................................')

    mp.analysis_for_acoustic_modelling(wav_file, out_feats_dir)
    return


def get_wav_filelist(wav_dir):
    wav_files = []
    for file in os.listdir(wav_dir):
        whole_filepath = os.path.join(wav_dir, file)
        if os.path.isfile(whole_filepath) and str(whole_filepath).endswith(".wav"):
            wav_files.append(whole_filepath)
        elif os.path.isdir(whole_filepath):
            wav_files += get_wav_filelist(whole_filepath)

    wav_files.sort()

    return wav_files

# FILES SETUP:========================================================================
lu.mkdir(out_dir)
l_wavfiles = get_wav_filelist(wav_dir)

# MULTIPROCESSING EXTRACTION:==========================================================
lu.run_multithreaded(feat_extraction, l_wavfiles, out_dir)

# For debugging (don't delete):
#for wavfile in l_wavfiles:
#    feat_extraction(wavfile, out_dir)


print('Done!')
        
